package com.bootdo.system.controller;

import com.bootdo.common.annotation.Log;
import com.bootdo.common.controller.BaseController;
import com.bootdo.common.utils.*;
import com.bootdo.system.domain.TMagazineDO;
import com.bootdo.system.domain.TMagazinePicturesDO;
import com.bootdo.system.service.TMagazinePicturesService;
import com.bootdo.system.service.TMagazineService;
import com.google.common.base.Throwables;
import com.google.common.collect.Lists;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.util.CollectionUtils;
import org.springframework.util.StringUtils;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.bind.annotation.RestController;

import javax.servlet.http.HttpServletRequest;
import java.io.File;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.concurrent.Callable;
import java.util.concurrent.ExecutionException;
import java.util.concurrent.FutureTask;

class MyCallable implements Callable<List> {
    private Logger log = LoggerFactory.getLogger(getClass());

    private List<TMagazineDO> magazines;
    private String keyword ;
    private String filePath ;

    public MyCallable(List<TMagazineDO> magazines,String keyword,String filePath) {
        this.magazines=Lists.newArrayList();
        this.magazines.addAll(magazines);
        this.keyword = keyword;
        this.filePath = filePath;
    }

    // 与run()方法不同的是，call()方法具有返回值
    @Override
    public List call() {
        List<TMagazineDO> results = Lists.newArrayList();
        try {
            if (!CollectionUtils.isEmpty(magazines)){
                for (TMagazineDO magazine : magazines) {
                    if (null!=magazine && !StringUtils.isEmpty(magazine.getFileContent())){
                        String pdfUrl = magazine.getFileContent();
                        String filename = pdfUrl.substring(pdfUrl.lastIndexOf("=")+1);
                        String path = filePath+filename;
                        log.info("搜索的pdf文件路径为：{}",path);
                        File pdfFile = new File(path);
                        if (pdfFile.exists()){
                            //先获取坐标
                            List<Map<String, Object>> wordInPdf = ItextpdfFindWordUtil.findWordInPdf(pdfFile, keyword);
                            List<Map<String, Object>> keyInfos = Lists.newArrayList();
                            if (!CollectionUtils.isEmpty(wordInPdf)){
                                //后获取文字
                                String content = ItextpdfUtil.getPdfContent(path);
                                int index = -1;
                                int length = content.length();
                                for (int i = 0; i < wordInPdf.size(); i++) {
                                    String keywordBrief = null;
                                    index = content.indexOf(keyword,index+1);
                                    if (index>0){
                                        if ((length-index)>20){
                                            keywordBrief = content.substring(index,index+20);
                                        }else {
                                            keywordBrief = content.substring(index,length);
                                        }
                                    }
                                    if (!StringUtils.isEmpty(keywordBrief)){
                                        Map<String, Object> keyInfo = wordInPdf.get(i);
                                        keyInfo.put("keyword",keyword);
                                        keyInfo.put("brief",keywordBrief);//关联文本内容
                                        keyInfos.add(keyInfo);
                                    }
                                }
                                log.info("搜索的杂志坐标为：{}",JacksonUtil.bean2Json(keyInfos));
                                magazine.setKeywordInfos(keyInfos);
                                results.add(magazine);
                            }else {
                                if (magazine.getTitle().contains(keyword) || magazine.getIssn().contains(keyword)){
                                    results.add(magazine);
                                }
                            }

                        }else {
                            if (magazine.getTitle().contains(keyword) || magazine.getIssn().contains(keyword)){
                                results.add(magazine);
                            }
                        }
                    }
                }
            }
            log.info("{}搜索结果：{}", Thread.currentThread().getName(),results.size());
        } catch (Exception e) {
            log.error("{}搜索异常：{}", Thread.currentThread().getName(),Throwables.getStackTraceAsString(e));
        }
        return results;
    }

}


/**
 * 搜索管理
 *
 * @auther: Ace Lee
 * @date: 2019/10/26 10:43
 */
@RestController
@RequestMapping("searchs")
public class SearchInfoController extends BaseController {
    private Logger log = LoggerFactory.getLogger(getClass());

    @Value("${bootdo.uploadPath}")
    private String filePath;

    @Autowired
    private TMagazineService tMagazineService;
    @Autowired
    private TMagazinePicturesService tMagazinePicturesService;

    @Log("搜索")
    @GetMapping("")
    public R get(HttpServletRequest request, @RequestParam(value = "keyword")String keyword) {

        try {
            Map<String, Object> map = new HashMap<>();
            map.put("offset",0);
            map.put("limit",5000);
            map.put("isValid","1");
            List<TMagazineDO> magazines = tMagazineService.list(map);
            int sum = CollectionUtils.isEmpty(magazines)?0:magazines.size();
            log.info("搜索的杂志总数为：{}",sum);
            if (StringUtils.isEmpty(keyword)) {
                String msg = JacksonUtil.bean2Json(magazines);
                return R.ok(msg);
            }

            List<FutureTask<List>> tasks = Lists.newArrayList();
            List<TMagazineDO> results = Lists.newArrayList();
            if (!CollectionUtils.isEmpty(magazines)) {
                int cilclesum = sum / 50;
                for (int i = 0; i < cilclesum + 1; i++) {
                    List<TMagazineDO> ciles = Lists.newArrayList();
                    if (i == cilclesum) {
                        ciles = magazines.subList(i * 50, sum);
                    } else {
                        ciles = magazines.subList(i * 50, (i + 1) * 50);
                    }
                    Callable<List> myCallable = new MyCallable(ciles, keyword, filePath);    // 创建MyCallable对象
                    FutureTask<List> ft = new FutureTask<List>(myCallable);

                    Thread thread = new Thread(ft);
                    thread.start();

                    tasks.add(ft);
                }

                if (tasks.size()>0){
                    for (FutureTask<List> task : tasks) {
                        try {
                            List list = task.get();
                            results.addAll(list);
                        } catch (InterruptedException e) {
                            e.printStackTrace();
                        } catch (ExecutionException e) {
                            e.printStackTrace();
                        }
                    }
                }

                log.info("搜索结果：{}", results.size());
                String msg1 = JacksonUtil.bean2Json(results);
                return R.ok(msg1);
            }
            return R.error();
        } catch (Exception e) {
            log.error("搜索异常：{}", Throwables.getStackTraceAsString(e));
        }
        return R.error();
    }

    private void setList(List<TMagazineDO> results, TMagazineDO magazine) {
//        Map<String, Object> pics1 = new HashMap<>(3);
//        pics1.put("magazineId", magazine.getId() + "");
//        List<TMagazinePicturesDO> pictures = tMagazinePicturesService.list(pics1);
//        log.info("搜索的杂志图片为：{}",CollectionUtils.isEmpty(pics1)?"null":JacksonUtil.bean2Json(pictures));
//        magazine.setPictures(pictures);
//        magazine.setContent("");
//        log.info("搜索的杂志信息为：{}",JacksonUtil.bean2Json(magazine));
        results.add(magazine);
    }


}
